using System;
using System.IO;
using System.Linq;
using UnityEditor;
using UnityEngine;

namespace EntityKit.Editor
{
    public class ScriptableObjectCreationWindow : EditorWindow
    {
        private string assetName = "NewConfig";
        private string assetPath = "Assets";
        private Type selectedType;
        
        private Vector2 scrollPosition;
        private string[] typeNames;
        private Type[] types;
        private int selectedIndex = 0;
        
        private string searchFilter = "";
        private string[] filteredTypeNames;
        private Type[] filteredTypes;
        private int[] originalIndices;
        private Vector2 typeListScrollPosition = Vector2.zero;
        
        // 样式定义
        private GUIStyle m_TitleStyle;
        private GUIStyle m_SubtitleStyle;
        private GUIStyle m_ButtonStyle;
        private GUIStyle m_SelectedItemStyle;
        private GUIStyle m_ListItemStyle;
        private GUIStyle m_SearchFieldStyle;
        private GUIStyle m_InfoBoxStyle;
        private GUIStyle m_PathFieldStyle;
        private GUIStyle m_SectionHeaderStyle;
        private GUIStyle m_ClearButtonStyle;
        private GUIStyle m_LabelStyle;
        
        private static Color SELECTED_COLOR = new Color(0.22f, 0.47f, 0.87f, 0.9f);
        private static Color HOVER_COLOR = new Color(0.3f, 0.3f, 0.3f, 0.5f);
        private static Color SECTION_BG = new Color(0.16f, 0.16f, 0.16f, 1.0f);
        
        private int hoveredIndex = -1;
        
        public static void ShowWindow()
        {
            var window = GetWindow<ScriptableObjectCreationWindow>("创建配置资源");
            window.minSize = new Vector2(450, 550);
            window.titleContent = new GUIContent("创建配置", EditorGUIUtility.IconContent("ScriptableObject Icon").image);
            window.Show();
        }
        
        private void OnEnable()
        {
            FindAllConfigTypes();
            UpdateFilteredTypes();
        }
        
        private void InitStyles()
        {
            if (m_TitleStyle == null)
            {
                m_TitleStyle = new GUIStyle(EditorStyles.largeLabel);
                m_TitleStyle.fontSize = 18;
                m_TitleStyle.fontStyle = FontStyle.Bold;
                m_TitleStyle.alignment = TextAnchor.MiddleCenter;
                m_TitleStyle.normal.textColor = new Color(0.9f, 0.9f, 0.9f);
                m_TitleStyle.margin = new RectOffset(5, 5, 10, 15);
            }
            
            if (m_SubtitleStyle == null)
            {
                m_SubtitleStyle = new GUIStyle(EditorStyles.label);
                m_SubtitleStyle.fontStyle = FontStyle.Bold;
                m_SubtitleStyle.fontSize = 12;
                m_SubtitleStyle.normal.textColor = new Color(0.8f, 0.8f, 0.8f);
                m_SubtitleStyle.margin = new RectOffset(5, 5, 5, 5);
            }
            
            if (m_ButtonStyle == null)
            {
                m_ButtonStyle = new GUIStyle(GUI.skin.button);
                m_ButtonStyle.padding = new RectOffset(15, 15, 8, 8);
                m_ButtonStyle.fontStyle = FontStyle.Bold;
                m_ButtonStyle.fontSize = 13;
                m_ButtonStyle.normal.textColor = Color.white;
            }
            
            if (m_SelectedItemStyle == null)
            {
                m_SelectedItemStyle = new GUIStyle();
                m_SelectedItemStyle.normal.background = MakeTex(2, 2, SELECTED_COLOR);
                m_SelectedItemStyle.normal.textColor = Color.white;
                m_SelectedItemStyle.padding = new RectOffset(10, 5, 5, 5);
                m_SelectedItemStyle.margin = new RectOffset(2, 2, 2, 2);
                m_SelectedItemStyle.border = new RectOffset(2, 2, 2, 2);
            }
            
            if (m_ListItemStyle == null)
            {
                m_ListItemStyle = new GUIStyle(EditorStyles.label);
                m_ListItemStyle.padding = new RectOffset(10, 5, 5, 5);
                m_ListItemStyle.margin = new RectOffset(2, 2, 2, 2);
                m_ListItemStyle.border = new RectOffset(2, 2, 2, 2);
                m_ListItemStyle.alignment = TextAnchor.MiddleLeft;
            }
            
            if (m_SearchFieldStyle == null)
            {
                m_SearchFieldStyle = new GUIStyle(EditorStyles.toolbarSearchField);
                m_SearchFieldStyle.margin = new RectOffset(5, 5, 0, 0);
                m_SearchFieldStyle.fixedHeight = 20;
                m_SearchFieldStyle.fontSize = 12;
            }
            
            if (m_ClearButtonStyle == null)
            {
                m_ClearButtonStyle = new GUIStyle(EditorStyles.miniButton);
                m_ClearButtonStyle.margin = new RectOffset(5, 5, 0, 0);
                m_ClearButtonStyle.fixedHeight = 20;
                m_ClearButtonStyle.fixedWidth = 50;
            }
            
            if (m_LabelStyle == null)
            {
                m_LabelStyle = new GUIStyle(EditorStyles.label);
                m_LabelStyle.fixedWidth = 80; // 固定标签宽度确保对齐
                m_LabelStyle.alignment = TextAnchor.MiddleLeft;
                m_LabelStyle.margin = new RectOffset(0, 0, 0, 0);
            }
            
            if (m_InfoBoxStyle == null)
            {
                m_InfoBoxStyle = new GUIStyle(EditorStyles.helpBox);
                m_InfoBoxStyle.padding = new RectOffset(10, 10, 10, 10);
                m_InfoBoxStyle.margin = new RectOffset(5, 5, 10, 5);
                m_InfoBoxStyle.wordWrap = true;
            }
            
            if (m_PathFieldStyle == null)
            {
                m_PathFieldStyle = new GUIStyle(EditorStyles.textField);
                m_PathFieldStyle.margin = new RectOffset(0, 0, 0, 0);
            }
            
            if (m_SectionHeaderStyle == null)
            {
                m_SectionHeaderStyle = new GUIStyle(EditorStyles.label);
                m_SectionHeaderStyle.fontStyle = FontStyle.Bold;
                m_SectionHeaderStyle.fontSize = 13;
                m_SectionHeaderStyle.normal.textColor = new Color(0.7f, 0.7f, 0.9f);
                m_SectionHeaderStyle.margin = new RectOffset(0, 0, 5, 5);
            }
        }
        
        private Texture2D MakeTex(int width, int height, Color col)
        {
            Color[] pix = new Color[width * height];
            for (int i = 0; i < pix.Length; i++)
                pix[i] = col;
            Texture2D result = new Texture2D(width, height);
            result.SetPixels(pix);
            result.Apply();
            return result;
        }
        
        void OnGUI()
        {
            InitStyles();
            
            // 主滚动视图
            scrollPosition = EditorGUILayout.BeginScrollView(scrollPosition);
            
            // 标题区域
            EditorGUILayout.LabelField("创建 ScriptableObject 配置", m_TitleStyle);
            EditorGUILayout.Space(5);
            
            // 搜索区域
            EditorGUILayout.LabelField("搜索类型", m_SectionHeaderStyle);
            EditorGUI.BeginChangeCheck();
            
            // 搜索框和清空按钮
            GUILayout.BeginHorizontal();
            {
                searchFilter = EditorGUILayout.TextField("", searchFilter, m_SearchFieldStyle, GUILayout.ExpandWidth(true));
                
                if (GUILayout.Button("清空", m_ClearButtonStyle))
                {
                    searchFilter = "";
                    GUI.FocusControl(null);
                }
            }
            GUILayout.EndHorizontal();
            
            if (EditorGUI.EndChangeCheck())
            {
                UpdateFilteredTypes();
            }
            
            EditorGUILayout.Space(10);
            
            // 类型选择区域
            EditorGUILayout.LabelField("可用类型", m_SectionHeaderStyle);
            
            Rect listRect = GUILayoutUtility.GetRect(0, 180, GUILayout.ExpandWidth(true));
            GUI.Box(new Rect(listRect.x - 1, listRect.y - 1, listRect.width + 2, listRect.height + 2), "", EditorStyles.helpBox);
            
            if (filteredTypes != null && filteredTypes.Length > 0)
            {
                typeListScrollPosition = GUI.BeginScrollView(listRect, typeListScrollPosition, 
                    new Rect(0, 0, listRect.width - 20, filteredTypes.Length * 22));
                
                for (int i = 0; i < filteredTypes.Length; i++)
                {
                    Rect itemRect = new Rect(0, i * 22, listRect.width - 20, 20);
                    
                    // 处理鼠标悬停
                    if (itemRect.Contains(Event.current.mousePosition))
                    {
                        hoveredIndex = i;
                        if (Event.current.type == EventType.MouseMove)
                            Repaint();
                        
                        if (Event.current.type == EventType.MouseDown && Event.current.button == 0)
                        {
                            selectedIndex = i;
                            selectedType = filteredTypes[selectedIndex];
                            assetName = selectedType.Name;
                            Event.current.Use();
                        }
                    }
                    
                    // 绘制背景
                    if (i == selectedIndex)
                    {
                        GUI.Box(itemRect, "", m_SelectedItemStyle);
                    }
                    else if (i == hoveredIndex)
                    {
                        GUI.Box(itemRect, "", GUI.skin.button);
                    }
                    
                    // 绘制类型名称
                    Rect textRect = new Rect(itemRect.x + 5, itemRect.y, itemRect.width - 5, itemRect.height);
                    GUI.Label(textRect, filteredTypeNames[i], m_ListItemStyle);
                }
                
                GUI.EndScrollView();
            }
            else
            {
                GUILayout.BeginHorizontal();
                GUILayout.FlexibleSpace();
                GUILayout.Label("未找到匹配的类型", EditorStyles.centeredGreyMiniLabel);
                GUILayout.FlexibleSpace();
                GUILayout.EndHorizontal();
            }
            
            EditorGUILayout.Space(15);
            
            // 资源命名区域 - 修复对齐
            EditorGUILayout.LabelField("资源配置", m_SectionHeaderStyle);
            
            // 使用水平布局确保标签和输入框对齐
            GUILayout.BeginHorizontal();
            GUILayout.Label("资源名称", m_LabelStyle, GUILayout.Width(80));
            assetName = EditorGUILayout.TextField(assetName, GUILayout.ExpandWidth(true));
            GUILayout.EndHorizontal();
            
            EditorGUILayout.Space(5);
            
            // 路径选择区域 - 修复对齐
            GUILayout.BeginHorizontal();
            GUILayout.Label("保存路径", m_LabelStyle, GUILayout.Width(80));
            assetPath = EditorGUILayout.TextField(assetPath, m_PathFieldStyle, GUILayout.ExpandWidth(true));
            if (GUILayout.Button("浏览", GUILayout.Width(60)))
            {
                var path = EditorUtility.OpenFolderPanel("选择保存路径", "Assets", "");
                if (!string.IsNullOrEmpty(path))
                {
                    if (path.StartsWith(Application.dataPath))
                    {
                        assetPath = "Assets" + path.Substring(Application.dataPath.Length);
                    }
                    else
                    {
                        EditorUtility.DisplayDialog("错误", "请选择项目Assets目录下的路径", "确定");
                    }
                }
            }
            GUILayout.EndHorizontal();
            
            EditorGUILayout.Space(15);
            
            // 创建按钮
            GUILayout.BeginHorizontal();
            GUILayout.FlexibleSpace();
            GUI.enabled = selectedType != null && !string.IsNullOrEmpty(assetName) && !string.IsNullOrEmpty(assetPath);
            if (GUILayout.Button("创建配置资源", m_ButtonStyle, GUILayout.Width(200)))
            {
                CreateAsset();
            }
            GUI.enabled = true;
            GUILayout.FlexibleSpace();
            GUILayout.EndHorizontal();
            
            EditorGUILayout.Space(10);
            
            // 类型信息区域
            if (selectedType != null)
            {
                EditorGUILayout.LabelField("类型信息", m_SectionHeaderStyle);
                EditorGUILayout.LabelField(selectedType.FullName, EditorStyles.wordWrappedMiniLabel);
            }
            
            EditorGUILayout.EndScrollView();
        }
        
        /// <summary>
        /// 查找所有继承自ScriptableObject的类型
        /// </summary>
        private void FindAllConfigTypes()
        {
            var configTypes = new System.Collections.Generic.List<Type>();
            
            foreach (var assembly in AppDomain.CurrentDomain.GetAssemblies())
            {
                try
                {
                    var typesInAssembly = assembly.GetTypes();
                    foreach (var type in typesInAssembly)
                    {
                        if (type.IsSubclassOf(typeof(ScriptableObject)) && !type.IsAbstract)
                        {
                            configTypes.Add(type);
                        }
                    }
                }
                catch (System.Exception)
                {
                    // 忽略无法加载的程序集
                }
            }
            
            types = configTypes.ToArray();
            typeNames = new string[types.Length];
            
            for (int i = 0; i < types.Length; i++)
            {
                typeNames[i] = string.IsNullOrEmpty(types[i].FullName) ? types[i].Name : types[i].FullName;
            }
            
            // 默认选中第一个
            if (types.Length > 0)
            {
                selectedType = types[0];
                assetName = selectedType.Name;
            }
            
            UpdateFilteredTypes();
        }
        
        /// <summary>
        /// 根据搜索过滤器更新类型列表
        /// </summary>
        private void UpdateFilteredTypes()
        {
            if (types == null || typeNames == null)
                return;
            
            if (string.IsNullOrEmpty(searchFilter))
            {
                filteredTypes = types;
                filteredTypeNames = typeNames;
                originalIndices = Enumerable.Range(0, types.Length).ToArray();
            }
            else
            {
                var filteredList = new System.Collections.Generic.List<(Type type, string name, int originalIndex)>();
                for (int i = 0; i < types.Length; i++)
                {
                    if (typeNames[i].Contains(searchFilter, StringComparison.OrdinalIgnoreCase) || 
                        types[i].Name.Contains(searchFilter, StringComparison.OrdinalIgnoreCase))
                    {
                        filteredList.Add((types[i], typeNames[i], i));
                    }
                }
                
                filteredTypes = filteredList.Select(x => x.type).ToArray();
                filteredTypeNames = filteredList.Select(x => x.name).ToArray();
                originalIndices = filteredList.Select(x => x.originalIndex).ToArray();
            }
            
            if (filteredTypes.Length > 0)
            {
                selectedIndex = Mathf.Clamp(selectedIndex, 0, filteredTypes.Length - 1);
                selectedType = filteredTypes[selectedIndex];
                assetName = selectedType.Name; 
            }
            else
            {
                selectedIndex = -1;
                selectedType = null;
            }
        }
        
        /// <summary>
        /// 创建ScriptableObject资源
        /// </summary>
        private void CreateAsset()
        {
            if (selectedType == null)
            {
                EditorUtility.DisplayDialog("错误", "请选择一个有效的类型", "确定");
                return;
            }
            
            if (string.IsNullOrEmpty(assetName))
            {
                EditorUtility.DisplayDialog("错误", "请输入资源名称", "确定");
                return;
            }
            
            if (string.IsNullOrEmpty(assetPath))
            {
                EditorUtility.DisplayDialog("错误", "请选择保存路径", "确定");
                return;
            }
            
            if (!assetPath.StartsWith("Assets"))
            {
                EditorUtility.DisplayDialog("错误", "保存路径必须在Assets目录下", "确定");
                return;
            }
            
            try
            {
                // 创建资源
                var asset = ScriptableObject.CreateInstance(selectedType);
                var fullPath = Path.Combine(assetPath, assetName + ".asset");
                
                // 确保目录存在
                var directory = Path.GetDirectoryName(fullPath);
                if (!Directory.Exists(directory))
                {
                    Directory.CreateDirectory(directory);
                }
                
                // 保存资源
                AssetDatabase.CreateAsset(asset, fullPath);
                AssetDatabase.SaveAssets();
                AssetDatabase.Refresh();
                
                // 在Project窗口中高亮显示新创建的资源
                var newAsset = AssetDatabase.LoadAssetAtPath<UnityEngine.Object>(fullPath);
                EditorUtility.FocusProjectWindow();
                Selection.activeObject = newAsset;
                
                Debug.Log($"成功创建配置资源: {fullPath}");
                
                Close();
            }
            catch (Exception ex)
            {
                Debug.LogError($"创建配置资源失败: {ex.Message}");
                EditorUtility.DisplayDialog("错误", $"创建失败: {ex.Message}", "确定");
            }
        }
    }
}